// Constants used as element IDs in the DOM
var DEFAULT_PANE = "default-pane";
var AUTHENTICATED_PANE = "authenticated-pane";
var AUTH_BUTTON = "auth-button"; 
var LOGOUT_BUTTON = "logout-button"; 
var SAVE_BUTTON = "save-button";
var EVENT_SELECT = "event-select";
var TITLE_FIELD = "title-field";
var DATE_FIELD = "date-field";
var LOCATION_FIELD = "location-field";
var ATTENDEES_FIELD = "attendees-field";
var NOTES_FIELD = "notes-field";
var STATUS_AREA = "status-area";
var ESTORE_HEADER = "mBuy-SA00831-";
var APP_NAME = "Moogle Buy System-0.1";
// Location of the event feed of the primary calendar for the authenticated user
var EVENT_FEED_URL = 
    "http://www.google.com/calendar/feeds/default/private/full";

// A google.gdata.calendar.CalendarService object that can be used to access
// private feed using AuthSub.
var myService;

// The events feed is retrieved once, and accessed every time the event
// selected in the dropdown menu is changed. 
var myEventsFeed;

/**
 * Sets the global calendar service to a new instance.  Also resets the form 
 * fields to clear out any information that may have been cached.
 */
function manage_order_init() {
  google.gdata.client.init(handleError);

  var token = google.accounts.user.checkLogin(EVENT_FEED_URL);
  // Write the token to the console for debug
  //google.gdata.util.log("token: '" + token + "'");

  myService = 
      new google.gdata.calendar.CalendarService(APP_NAME);

  var authButton = document.getElementById(AUTH_BUTTON);
  if (google.accounts.user.checkLogin(EVENT_FEED_URL)) {
    document.getElementById(DEFAULT_PANE).style.display = "none";
    document.getElementById(AUTHENTICATED_PANE).style.display = "inline";
    getEvents();
  } else {
    document.getElementById(DEFAULT_PANE).style.display = "inline";
    document.getElementById(AUTHENTICATED_PANE).style.display = "none";
  } 
  reset();
}

/**
 * Requests an AuthSub token for interaction with the Calendar service.
 */
function login() {
  var token = google.accounts.user.login(EVENT_FEED_URL);
}

/**
 * Revokes the AuthSub token and resets the page.
 */
function logout(){
  google.accounts.user.logout();
  manage_order_init();
}

/**
 * Submits a query for all events that occur today.
 */
function getEvents() {
  var query = new google.gdata.calendar.CalendarEventQuery(EVENT_FEED_URL);

  // Set the start-min parameter to the beginning of today.
  var todayDate = new Date();
  todayDate.setHours(0);
  todayDate.setMinutes(0);
  todayDate.setSeconds(0);
  todayDate.setMilliseconds(0);
  var today = new google.gdata.DateTime(todayDate, false);
  query.setMinimumStartTime(google.gdata.DateTime.toIso8601(today));
  query.setFullTextQuery(ESTORE_HEADER);

  // Set the start-max parameter to the beginning of tomorrow.
  var tomorrowDate = new Date();
  tomorrowDate.setDate(todayDate.getDate() + 1);
  tomorrowDate.setHours(0);
  tomorrowDate.setMinutes(0);
  tomorrowDate.setSeconds(0);
  tomorrowDate.setMilliseconds(0);
  var tomorrow = new google.gdata.DateTime(tomorrowDate, false);
  query.setMaximumStartTime(google.gdata.DateTime.toIso8601(tomorrow));

  // Write the uri to the console for debugging
  //google.gdata.util.log("uri=" + query.getUri());
  myService.getEventsFeed(query, handleEventsFeed, handleError);
}

/**
 * Populates the dropdown menu with events returned in the query for
 * today's events.
 *
 * @param {JSON} The JSON object returned by the Calendar service that
 *   contains a collection of event entries.
 */
function handleEventsFeed(myResultsFeedRoot) {
  var eventList = document.getElementById(EVENT_SELECT);
  eventList.onchange = loadEvent;
  eventList.disabled = false; 
  eventList.options[eventList.selectedIndex].disabled = true; 
  eventList.options[eventList.selectedIndex].text = "選擇...";
  
  myEventsFeed = myResultsFeedRoot.feed;
  events = myEventsFeed.getEntries();
  for (var i = 0; i < events.length; i++) {
    var option = document.createElement("option");
    eventTitle0 = events[i].getTitle().getText();
    if(eventTitle0.indexOf(ESTORE_HEADER) !== 0)
      continue;
    var eventTitle = eventTitle0.substring(ESTORE_HEADER.length);
    option.value = i;
    option.appendChild(document.createTextNode(eventTitle));
    eventList.appendChild(option);
  }
}

/**
 * Populates the event information fields with data from the selected event
 * entry. 
 */
function loadEvent() {
  setStatus();

  var saveButton = document.getElementById(SAVE_BUTTON);
  saveButton.disabled = false;

  var eventList = document.getElementById(EVENT_SELECT);

  // If the first option (Select...) is selected, don't do anything
  if (eventList.selectedIndex === 0) {
    return;
  }
  var eventIndex = eventList.options[eventList.selectedIndex].value;
  var event = myEventsFeed.getEntries()[eventIndex];

  var title = document.getElementById(TITLE_FIELD);
  title.value = event.getTitle().getText();

  var date = document.getElementById(DATE_FIELD);
  date.value = event.getTimes()[0].getStartTime().getDate();

  var theLocation = document.getElementById(LOCATION_FIELD);
  theLocation.value = event.getLocations()[0].getValueString();
  if (theLocation.value == "undefined") {
    theLocation.value = "";
  }

  var attendeesDiv = document.getElementById(ATTENDEES_FIELD);
  attendeesDiv.innerHTML = "";

  var participants = event.getParticipants();
  for (var i = 0; i < participants.length; i++) {
    var element = document.createElement("div");
    element.innerHTML = participants[i].getEmail();
    attendeesDiv.appendChild(element);
  }
  
  var notes = document.getElementById(NOTES_FIELD);
  notes.value = event.getContent().getText();
  if (notes.value == "undefined") {
    notes.value = "";
  }
}

/**
 * Updates the event in Google Calendar with the data in the event information
 * fields.
 */
function saveEvent() {
  var eventList = document.getElementById(EVENT_SELECT);
  var eventIndex = eventList.options[eventList.selectedIndex].value;
  var event = myEventsFeed.getEntries()[eventIndex];

  var title = document.getElementById(TITLE_FIELD).value;
  event.getTitle().setText(title);
  
  var date = new Date(document.getElementById(DATE_FIELD).value);
  event.setTimes(null);
  var when = new google.gdata.When();
  when.setStartTime(date);
  when.setEndTime(date); 
  event.addTime(when);
  
  var theLocation = document.getElementById(LOCATION_FIELD).value;
  event.getLocations()[0].setValueString(theLocation);
  
  var notes = document.getElementById(NOTES_FIELD).value;
  event.getContent().setText(notes);  

  event.updateEntry(handleSaveSuccess, handleSaveError);
}

/**
 * Updates the appropriate entry in myEventsFeed and notifies the user that 
 * the event was saved.
 */
function handleSaveSuccess(entryRoot) {
  var eventList = document.getElementById(EVENT_SELECT);
  var option = eventList.options[eventList.selectedIndex];
  option.text = entryRoot.entry.getTitle().getText();
  var eventIndex = option.value;
  myEventsFeed.getEntries()[eventIndex] = entryRoot.entry;
  setStatus("更新完成");
}

/**
 * Sets the status to the given string.  If none is given, then the status is
 * cleared.
 */
function setStatus(msg) {
  var eventStatus = document.getElementById(STATUS_AREA);
  if (msg) {
    eventStatus.innerHTML = msg;
  } else {
    eventStatus.innerHTML = "";
  }
}

/**
 * Notifies the user that the event was not saved.
 */
function handleSaveError(e) {
  setStatus("Error");
  handleError(e);
}

/**
 * Creates a popup alert to notify the user of a Google data related error.
 * 
 * @param {Object} An error that occurred while attempting to interact with
 *   the Google Calendar service.  
 */
function handleError(e) {
  if (e instanceof Error) {
    // Alert with the error line number, file and message.
    alert('Error at line ' + e.lineNumber +
        ' in ' + e.fileName + '\n' +
        'Message: ' + e.message);
    // If available, output HTTP error code and status text
    if (e.cause) {
      var errorStatus = e.cause.status;
      var statusText = e.cause.statusText;
      alert('Root cause: HTTP error ' + errorStatus + ' with status text of: ' +
          statusText);
    }
  } else {
    alert(e.toString());
  }
}

/**
 * Resets the form back to the same state as when the page first loads. 
 */
function reset() {
  var saveButton = document.getElementById(SAVE_BUTTON);
  saveButton.disabled = true;

  var eventList = document.getElementById(EVENT_SELECT); 
  eventList.options[0].disabled = false; 
  eventList.options[0].text = "更新中...";
  while (eventList.length > 1) {
     eventList.remove(1);
  }
  eventList.disabled = true;
  
  document.getElementById(TITLE_FIELD).value = "";
  document.getElementById(DATE_FIELD).value = "";
  document.getElementById(LOCATION_FIELD).value = "";
  var attendeesDiv = document.getElementById(ATTENDEES_FIELD);
  attendeesDiv.innerHTML = "";
  document.getElementById(NOTES_FIELD).value = "";
}
